/**
 * NewsCatalogServiceImpl.java
 * @author
 * 作者 屈甲康 
 */
package org.jackysoft.service.impl;

import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;

import org.jackysoft.entity.AcegiRole;
import org.jackysoft.entity.User;
import org.jackysoft.entity.nosql.NewsCatalog;
import org.jackysoft.google.collection.ZTreeNode;
import org.jackysoft.portal.google.collection.NewsCatalogZtreeFunction;
import org.jackysoft.service.AbstractNoSqlServiceImpl;
import org.jackysoft.service.NewsCatalogService;
import org.jackysoft.service.NewsInfoService;
import org.jackysoft.util.SpringSecurityUtils;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.springframework.dao.DataAccessException;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import com.google.common.collect.Collections2;
import com.google.common.collect.Maps;
import com.mongodb.BasicDBObject;
import com.mongodb.BasicDBObjectBuilder;
import com.mongodb.DBObject;

@Service
public class NewsCatalogServiceImpl extends AbstractNoSqlServiceImpl<NewsCatalog>implements NewsCatalogService {

  

	/**
	 * 
	 */
	private static final long serialVersionUID = -3003220194978748364L;
    private NewsInfoService infoService;
	public NewsCatalogServiceImpl(){
	   this.type = NewsCatalog.class;
	}

	
	

	@Override
	public void remove(NewsCatalog obj) {
		removeByParent(obj.getId());
	}

	void removeByParent(String parent){
		
		List<NewsCatalog> list = this.findAll(BasicDBObjectBuilder.start("parentId", parent).get());
        if(CollectionUtils.isEmpty(list)){
        	infoService.removeByCatalog(parent);
            super.remove(parent);	
        }else{
        	for(NewsCatalog nc:list){
        		removeByParent(nc.getId());
        	}
        }
	}



	@Override
	public Collection<NewsCatalog> getsByParent(String parent)
			throws DataAccessException {
		User user = SpringSecurityUtils.getCurrentUser();
		DBObject query = new BasicDBObject("parentId",parent);
		//TODO 个人权限控制
		DBObject sort = new BasicDBObject("sort","asc");
		
		Collection<NewsCatalog> catas = this.getsAndSort(query, sort);
		for(NewsCatalog c : catas){
			Collection<NewsCatalog> children = getsByParent(c.getId());
			boolean leaf = CollectionUtils.isEmpty(children);
			c.setLeaf(leaf);
			c.setChildren(children);
		}
		return catas;
	}



	@Override
	public boolean isParent(String sid) {
	
		Collection<NewsCatalog> catas  = getsByParent(sid);
		return !CollectionUtils.isEmpty(catas);
	}



	@Override
	public Map<String,String> tops() throws DataAccessException {
		DBObject query = new BasicDBObject("parentId","root");
		DBObject sort = new BasicDBObject("sort","asc");
		
		Collection<NewsCatalog> catas = this.getsAndSort(query, sort);
		Map<String,String> map = Maps.newHashMap();
		for(NewsCatalog nc:catas){
			map.put(nc.getName(), nc.getId());
		}
		return map;
	}

	@Override
	public String topMenus(String sid,String firstChildId) throws DataAccessException {
		NewsCatalog parent = this.getBySid(sid);
		Document doc = Jsoup.parse("");
		Element div = doc.createElement("div").addClass("navbar");
		Element div1 = doc.createElement("div").addClass("navbar-inner");
		div.appendChild(div1);
		Element div2 = doc.createElement("div").addClass("container");
		div1.appendChild(div2);
		Element alink = doc.createElement("a")
		   .attr("href", "javascript:;")
		   .addClass("btn")
		   .addClass("btn-navbar")
		   .attr("data-target",".nav-collapse")
		   .attr("data-toggle","collapse");
		Element span1 = doc.createElement("span").addClass("icon-bar");
		Element span2 = span1.clone();
		Element span3 = span1.clone();
		alink.appendChild(span3).appendChild(span2).appendChild(span1);
		div2.appendChild(alink);
		Element aname = doc.createElement("a")
				.text(parent.getName())
				.attr("href", "javascript:;")
				.addClass("brand");
		div2.appendChild(aname);
		Element div3 = doc.createElement("div").addClass("nav-collapse");
		div2.appendChild(div3);
		Element ullist  = doc.createElement("ul").addClass("nav");
		div3.appendChild(ullist);
		
		Collection<NewsCatalog> children = parent.getChildren();
		for(NewsCatalog cnc : children){
			ullist.appendChild(childrenMenu(cnc,doc,firstChildId));
		}
		
		return div.outerHtml();
	}
	
	/**
	 * 二级菜单
	 * */
	Element childrenMenu(NewsCatalog nc,Document doc,String firstChildId){
		Collection<NewsCatalog> children =  nc.getChildren();
		int size = children.size();
		
		Element li = doc.createElement("li");
		if(nc.getId().equals(firstChildId))
			li.addClass("active");
		if(size==0){
			
			Element a = doc.createElement("a")
					.attr("href", "javascript:;")
					.attr("childId", nc.getId())
					.addClass("childdata")
					.text(nc.getName());
			li.appendChild(a);
		
		}else{
			li.addClass("dropdown");
			//<a data-toggle="dropdown"	class="dropdown-toggle" href="#">Dropdown <b class="caret"></b></a>
			Element a = doc.createElement("a")
					.attr("data-toggle", "dropdown")
					.attr("href", "javascript:;")
					.addClass("dropdown-toggle")
					.text(nc.getName());
			Element b = doc.createElement("b").addClass("caret");
			a.appendChild(b);
			li.appendChild(a);
			Element ul = doc.createElement("ul").addClass("dropdown-menu");
			li.appendChild(ul);
			for(NewsCatalog ncc:children){
				Element cli  = doc.createElement("li");
				Element clia = doc.createElement("a")
				.addClass("childdata")
			    .attr("href", "javascript:;")
			    .attr("parentId",nc.getId())
			    .attr("childId",ncc.getId())
				.text(ncc.getName());
			    cli.appendChild(clia);
			    ul.appendChild(cli);
			}
		}
		
		return li;
		
	}



	@Override
	public NewsCatalog getBySid(String sid) throws DataAccessException {
		NewsCatalog me = this.get(sid);
		Collection<NewsCatalog> children = getsByParent(sid);
		boolean leaf = CollectionUtils.isEmpty(children);
		me.setLeaf(leaf);
		me.setChildren(children);
		return me;
	}



	@Override
	public String tops(String name) throws DataAccessException {
		return tops().get(name);
	}



	@Override
	public Collection<ZTreeNode> getsZtreeNodes(String parentSid)
			throws DataAccessException {
		
		Collection<NewsCatalog> ncs = onlyByParent(parentSid);
		org.jackysoft.util.CollectionUtils.notNullable(ncs);
		Collection<ZTreeNode>  ztrees = Collections2.transform(ncs, new NewsCatalogZtreeFunction());
		return ztrees;
	}
		
    Collection<NewsCatalog> onlyByParent(String parent)
			throws DataAccessException {
    	DBObject query = new BasicDBObject("parentId",parent);
		DBObject sort = new BasicDBObject("sort","asc");
		
		Collection<NewsCatalog> catas = this.getsAndSort(query, sort);
		for(NewsCatalog c : catas){
			Collection<NewsCatalog> children = onlyByParent(c.getId());
			boolean leaf = CollectionUtils.isEmpty(children);
			c.setLeaf(leaf);					
		}
		return catas;
	}



	@Override
	public String getDefaultChildId(String sid) throws DataAccessException {
		Collection<NewsCatalog> ncs = this.onlyByParent(sid);
		Iterator<NewsCatalog> itr = ncs.iterator();
		if(itr.hasNext())
			return itr.next().getId();
		
		return null;
	}

    @Resource
	public void setInfoService(NewsInfoService infoService) {
		this.infoService = infoService;
	}
}